/*
 * Copyright (c) 2018, apexes.net. All rights reserved.
 *
 *         http://www.apexes.net
 *
 */
package net.apexes.commons.lang;

import java.util.ArrayList;
import java.util.List;

/**
 * 分页辅助类
 * 
 * @author <a href="mailto:hedyn@foxmail.com">HeDYn</a>
 *
 * @param <T>
 */
public class PageableHelper<T> {

    private final List<T> datas;
    private List<T> originals;
    private int pageSize;
    private int pageCount;
    private int currentPageIndex;

    public PageableHelper() {
        this(8);
    }

    public PageableHelper(int pageSize) {
        this(null, pageSize);
    }

    public PageableHelper(List<T> originals, int pageSize) {
        this.datas = new ArrayList<>();
        setOriginals(originals, pageSize);
    }

    public final void setOriginals(List<T> originals) {
        setOriginals(originals, pageSize);
    }

    public final void setOriginals(List<T> originals, int pageSize) {
        if (pageSize <= 0) {
            throw new IllegalArgumentException("The pageSize must be greater than 0.");
        }
        this.originals = originals;
        this.pageSize = pageSize;
        datas.clear();
        if (originals != null && !originals.isEmpty()) {
            datas.addAll(originals);
        }
        int size = datas.size();
        if (size == 0) {
            pageCount = 0;
        } else {
            pageCount = (size - 1) / pageSize + 1;
        }
        currentPageIndex = 0;
    }

    public final List<T> getOriginals() {
        return originals;
    }

    /**
     * 返回总页数
     * @return
     */
    public int getPageCount() {
        return pageCount;
    }

    /**
     * 返回每页的最大元素个数
     * @return
     */
    public int getPageSize() {
        return pageSize;
    }

    /**
     * 返回当前页序号
     * @return
     */
    public int getCurrentPageIndex() {
        return currentPageIndex;
    }

    /**
     *
     * @return
     */
    public boolean isEmpty() {
        return datas.isEmpty();
    }

    /**
     * 是否还有前一页
     * @return 如果当前页已经是第一页返回 false
     */
    public boolean hasPageUp() {
        return currentPageIndex > 0;
    }

    /**
     * 前翻一页并返回翻页后的内容
     * @return 如果翻页前已经处于第一页返回 null
     */
    public List<T> pageUp() {
        if (hasPageUp()) {
            currentPageIndex--;
            return get(currentPageIndex);
        }
        return null;
    }

    /**
     * 是否还有后一页
     * @return 如果当前页已经是最后一页返回 false
     */
    public boolean hasPageDown() {
        return currentPageIndex < pageCount - 1;
    }

    /**
     * 后翻一页并返回翻页后的内容
     * @return 如果翻页前已经处于最后一页返回 null
     */
    public List<T> pageDown() {
        if (hasPageDown()) {
            currentPageIndex++;
            return get(currentPageIndex);
        }
        return null;
    }

    /**
     * 返回当前页的内容
     * @return
     */
    public List<T> get() {
        return get(currentPageIndex);
    }

    /**
     * 返回指定页中的元素
     * @param pageIndex
     * @return
     */
    public List<T> get(int pageIndex) {
        if (datas.isEmpty()) {
            return null;
        }
        int bi = pageIndex * pageSize;
        int ei = Math.min(datas.size(), bi + pageSize);
        return datas.subList(bi, ei);
    }

    /**
     *
     * @return
     */
    public boolean isFirst() {
        return currentPageIndex == 0;
    }

    /**
     * 翻到第一页
     */
    public void toFirst() {
        currentPageIndex = 0;
    }

    /**
     *
     * @return
     */
    public boolean isEnd() {
        if (pageCount == 0) {
            return currentPageIndex == 0;
        } else {
            return currentPageIndex == pageCount - 1;
        }
    }

    /**
     * 翻到最后一页
     */
    public void toEnd() {
        if (pageCount == 0) {
            currentPageIndex = 0;
        } else {
            currentPageIndex = pageCount - 1;
        }
    }
}
